from etgui import *
from PyWizard import WizPage
from ShowHTML import ShowHTML,ShowDocu,escape
import SetupWizStrings
import FlexLMErrors
reload(SetupWizStrings)
from SetupWizStrings import *
import os,string,sys,regsub
gTitleFont=Font(eFontHelvetica,16,eFaceBold)
gIsWindows=sys.platform=='win32'
class WinEnviron:
	def __init__(self):
		dict={}
		for k,v in os.environ.items():
			dict[string.upper(k)]=v
		self.dict=dict
	def __getitem__(self,name):
		return self.dict[string.upper(name)]
if gIsWindows:
	ENVIRON=WinEnviron()
else:
	ENVIRON=os.environ
class WizPageLayout:
	def MakeContent(self,page):
		items=[]
		self.AddHeader(items,page)
		self.AddExplain(items,page)
		self.AddContent(items,page)
		return self.MakePage(items,page)
	def AddHeader(self,items,page):
		if page.header:
			header=self.MakeHeader(page)
			items.append(header)
 
	def MakeHeader(self,page):
		header=MultilineTextItem("@B%s@B"%page.header)
		return header
	def AddExplain(self,items,page):
		if page.explain:
			explain=self.MakeExplain(page)
			items.append(explain)
	def MakeExplain(self,page):
		return MultilineTextItem(page.explain,300)
	def AddContent(self,items,page):
		content=page.DoMakeContent()
		if content:
			content=self.MakePageContent(content)
			items.append(content)
	def MakePageContent(self,content):
		return AlignBox(eVObjVExpand|eVObjVCenter,content)
	def MakePage(self,items,page):
		box= VBox(align=eVObjVExpand, 
			gap=gPoint2, 
			items=items
		)
		return box

class WizPageLayout2(WizPageLayout):
	def MakeHeader(self,page):
		header=AlignBox(eVObjHCenter,TextItem(-1,page.header,gTitleFont),gInkWhite)
		header.SetFlag(eVObjVFixed)
		return header
class WizPageLayout3(WizPageLayout):
	def MakeHeader(self,page):
		header=AlignBox(eVObjHCenter,TextItem(-1,page.header,gTitleFont),gInkWhite)
		header.SetFlag(eVObjVFixed)
		return header
	def MakePage(self,items,page):
		box= VBox(align=eVObjVExpand|eVObjHExpand|eVObjHCenter, 
			gap=gPoint2, 
			items=items
		)
		return box
		return AlignBox(eVObjVExpand|eVObjVCenter|eVObjHExpand|eVObjHCenter,box)
class WizPageLayout4(WizPageLayout):
	def MakeExplain(self,page):
		return AlignBox(eVObjHCenter,MultilineTextItem(page.explain))
	def MakeHeader(self,page):
		header=AlignBox(eVObjHCenter,MultilineTextItem("@B%s@B"%page.header))
		return header
	def MakePageContent(self,content):
		return AlignBox(eVObjVExpand|eVObjVCenter|eVObjHCenter,content)
	def MakePage(self,items,page):
		box= VBox(align=eVObjVExpand|eVObjHExpand|eVObjHCenter, 
			gap=gPoint2, 
			items=items
		)
		return box
class WizPageLayout5(WizPageLayout4):
	def MakeHeader(self,page):
		header=AlignBox(eVObjHCenter,TextItem(-1,page.header,gTitleFont),gInkWhite)
		header.SetFlag(eVObjVFixed)
		return header
########################################################################
gLayout=WizPageLayout()

class SetupWizPage(WizPage):
	def __init__(self,task=None):
		self.help=self.s_help
		self.header=self.s_header
		self.explain=self.s_explain
		self.box=AlignBox(eVObjVExpand|eVObjHExpand,Filler(gPoint1))
		WizPage.__init__(self,self.s_name,task)
	def CanShowHelp(self):
		return self.s_help!=''
	def ShowHelp(self):
		ShowHTML(self.s_help)
	def MakeContent(self):
		return gLayout.MakeContent(self)
		self.ResetContent()
		return self.box
	def DoMakeContent(self):
		return TextItem("Abstract????")
#	def EditBegin(self):
#		self.ResetContent()
	def ResetContent(self):
		self.box.SetAt(0,gLayout.MakeContent(self))
 

class AbstrCheckPage(SetupWizPage):
	firstId=10000
	def DoMakeContent(self):
		items=[]
		id=self.firstId
		for e in self.GetCheckedItems():
			items.append(self.MakeNameVObj(id,e))
			items.append(self.MakeValueVObj(id,e))
			id=id+1
		return Form(items=items)
	def GetCheckedItems(self):
		raise RuntimeError, "AbstractMethod"
	def MakeNameVObj(self,id,element):
		return element.MakeName()
	def MakeValueVObj(self,id,element):
		return element.MakeValue()
	def WantToBeDisplayed(self):
		for i in self.GetCheckedItems():
			if not i.IsOk():
				return 1
		return self.model.showpages
	def MakeDetail(self,item):
		info=item.GetInfo()
		name=item.GetName()
		return self.s_detail_html % vars()
	def MakeDescription(self):
		return ""
class AbstrCheckButtonPage(AbstrCheckPage):
	def MakeValueVObj(self,id,element):
		b=ActionButton(id,self.s_details)
		b.SetFlag(eVObjHFixed)
		return HExpander(items=(element.MakeValue(),Filler(gPoint1),b))
	def Control(self,id,part,val):
		i=id-self.firstId
		if i>=0:
			ShowHTML(self.MakeDetail(self.GetCheckedItems()[i]))
		return 1
class AbstrCheckButtonPage(AbstrCheckPage):
	def DoMakeContent(self):
		form=AbstrCheckPage.DoMakeContent(self)
		return VBox(items=(form,ActionButton(12345,self.s_details)))
	def Control(self,id,part,val):
		if id==12345:
			ShowHTML(self.MakeDetails())
		return 1
	def MakeDetails(self):
		details=""
		for item in self.GetCheckedItems():
			details=details+self.MakeDetail(item)
		name=self.name
		description=self.MakeDescription()
		return self.s_details_html % vars()
########################################################################
def cutstr(value,n,dots='...'):
	v=repr(value)
	if n and len(v)>n:
		v=v[:(n-2)/2]+dots+v[-(n-2)/2:]
	return str(v)

class CheckableItem(SWCheck):
	def __init__(self,name,explain=""):
		self.name=name
		self.s_explain=explain
		self.error=None
		self.value=None
		if self.Check():
			self.CheckValue(self.value)
	def Check(self):
		return 1
	def CheckValue(self,value):
		self.status="The value is: @b%s@b" % `value`
	def IsOk(self):
		return self.error is None
	def MakeName(self):
		name=self.GetName()
		if self.error:
			format=self.s_error_name_format
		else:
			format=self.s_normal_name_format
		return MultilineTextItem(format %name)
	def MakeValue(self):
		if self.error:
			return self.MakeErrorValue()
		return self.MakeNormalValue()
	def MakeErrorValue(self):
		return MultilineTextItem(self.s_error_format % self.error)
	def MakeNormalValue(self):
		return MultilineTextItem(self.s_normal_format % self.s_check_ok)
	def GetName(self):
		return self.name
	def GetInfo(self):
		return self.info

if IsWindows():
	def pathisequal(s1,s2):
		return string.lower(s1)==string.lower(s2)
else:
	def pathisequal(s1,s2):
		return s1==s2

class EnvVar(SWCheckEnvVar,CheckableItem):
	def __init__(self,name,explain="",value=None):
		self.exp_value=value
		CheckableItem.__init__(self,name,explain)
	def Check(self):
		try:
			v=ENVIRON[self.name]
		except KeyError:
			v=None
		info=self.VariableInfo(v)
		if v is None:
			err="Variable not set."
		else:
			err=self.CheckVariable(v)
		if err:
			self.error=self.s_error
			self.value=None
			if info:
				self.info=info+err
			else:
				self.info=err
		else:
			self.value=v
			self.info=info
		return 1
	def VariableInfo(self,value):
		if value is not None:
			return "<DL><DT>Variable was set to <DD><code>%s</code></DL>"%value
		else:
			return ""
	def CheckVariable(self,value):
		if self.exp_value is None:
			return None
		if not self.IsEqualValue(value,self.exp_value):
			return "Expected value <code>%s</code>" % self.exp_value
	def IsEqualValue(self,v1,v2):
		return v1==v2
class EnvVarFile(EnvVar):
	def CheckVariable(self,value):
		retval=EnvVar.CheckVariable(self,value)
		if retval:
			return retval
		if not os.path.isfile(value):
			return "File <code>%s</code> does not exist!" % value
	def IsEqualValue(self,v1,v2):
		return pathisequal(v1,v2)
class EnvVarDir(EnvVarFile):
	def CheckVariable(self,value):
		retval=EnvVar.CheckVariable(self,value)
		if retval:
			return retval
		if not os.path.isdir(value):
			return "<code>%s</code> is not a directory!" % value
 
class PathVar(EnvVar):
	def Check(self):
		retval=EnvVar.Check(self)
		if retval:
			dirs=string.split(self.info,os.pathsep)
			bindir=reduce(os.path.join, (GetSniffDir(),"bin"))
			def repl(path,dir=bindir):
				try:
					if os.path.samefile(path,dir):
						return "<B>%s</B>"%path
				except os.error:
					pass
				return path
			dirs=map(repl,dirs)
			self.info=string.join(dirs,"<BR>")
		return retval
class WinPathVar(EnvVar):
	def __init__(self,name,p1):
		self.p1=string.lower(p1)
		EnvVar.__init__(self,name)
	def Check(self):
		retval=EnvVar.Check(self)
		info=''
		if retval:
			dirs=string.split(self.value,os.pathsep)
			dirslower=map(string.lower,dirs)
			try:
				dirslower.index(string.lower(self.p1))
			except:
				try:
					dirslower.index(string.lower(gSystem.ConvertLongToShortPath(self.p1)))
				except:
					info="<DL><DT>Missing directory<DD><code>%s</code></DL>" %self.p1
					self.error=self.s_error
			def repl(path,dir=self.p1):
				if string.lower(path) == dir:
					return "<B>%s</B>"%path
				if string.lower(path) == string.lower(gSystem.ConvertLongToShortPath(dir)):
					return "<B>%s</B>"%path
				return path
			dirs=map(repl,dirs)
			var=string.join(dirs,"<BR>")
			self.info=info+self.VariableInfo(var)
		return retval
class FileFinder:
	def __init__(self):
		progs={}
		for p in self.GetPathlist():
			if p == '.':
				p=os.getcwd()
			try:
				files=os.listdir(p)
			except:
				files=[]
			for f in files:
				if not progs.has_key(f):
					progs[f]=[p]
				else:
					progs[f].append(p)
		self.progs=progs
	def Find(self,name):
		if self.progs.has_key(name):
			return self.progs[name]
		return []
	def GetPathlist(self):
		try:
			path=ENVIRON["PATH"]
		except KeyError:
			return []
		return string.split(path,os.pathsep)
gFileFinder=FileFinder()
class ParserTool(SWCheckTool,CheckableItem):
	def __init__(self,name,executable,tutorial=''):
		self.tutorial=tutorial
		if gIsWindows:
			executable=executable+'.exe'
		self.executable=executable
		CheckableItem.__init__(self,name)
	def Check(self):
		paths=gFileFinder.Find(self.executable)
		if not paths:
			self.error=self.s_error
			self.value=None
			self.info=self.error
			self.installed=0
			return 0
		self.value=paths
		self.installed=1
		self.info=string.join(paths,"\n")
		return 1
	def GetName(self):
		return self.name + self.s_parser

class InstalledFile(SWCheckFile,CheckableItem):
	def __init__(self,name,filename,explain=""):
		#print string.split(filename,'/')
		self.filename=filename
		CheckableItem.__init__(self,name,explain="")
	def Check(self):
		path=os.path.join(GetSniffDir(),self.filename)
		if not os.path.exists(path):
			self.error=self.s_error
			self.value=None
			self.info=self.error
			self.installed=0
			return 0
		self.value=path
		self.installed=1
		self.info=os.path.join("$SNIF_DIR",self.filename)
		return 1

class LicenseTool(SWCheckLicense,CheckableItem):
	info=''
	def __init__(self,feature,name,explain=""):
		self.feature=feature
		CheckableItem.__init__(self,name,explain="")
	def Check(self):
		v=SLicenseGetVersion()
		#v="2.3"
		fn=SLicenseGetFeatureNames(self.feature)
		#print fn
		if not fn:
			self.error=self.s_licesne_no_feature
			self.info=self.error
			self.value=None
			self.installed=0
			return 1
		else:
			fail=""
			for subfeature in fn:
				(ok,info,msg)=self.CheckSubFeature(v,subfeature)
				#print self.feature,subfeature,ok
				if ok:				
					self.value=subfeature
					self.info= info+msg
					return 1
				fail=fail+"<h4>"+subfeature+"</h4>"+info+msg
			self.error=self.s_error
			self.info=fail
			return 0
	def CheckSubFeature(self,v,subfeature):
		fn=[subfeature]
		f=LMFeature(self.feature,v,fn)
		f.Refresh()
		msg=f.GetLicenseMsg()
		msg="<pre>%s</pre>" %escape(msg)
		if not f.Ok():
			return 0,self.TranslateError(f.LastError(),fn),msg
		info= "You got the feature <b>%s</b>" %subfeature
		f.Free()
		return 1,info,msg
	def TranslateError(self,errormsg,fn):
		import regex
		reg=regex.compile("\([^(]+\)(\(-[0-9]+\)[^)]+)\(.*\)")
		if reg.match(errormsg)<=0:
			return "<strong>%s</strong>" %errormsg
		no=string.atoi(reg.group(2))
		explain=FlexLMErrors.GetErrorString(no)
		explain=escape(explain)
		explain=regsub.gsub('\n\n','\n<p>',explain)
		details=reg.group(3)
		if details:
			details=": "+details
		return "<b>%s</b> %s<br>%s" %(reg.group(1),details,explain)# + "<p>"+errormsg

class LicenseParserTool(LicenseTool):
	def GetName(self):
		return self.name + self.s_parser
def GetLicenseDescription():
	return "<pre>%s</pre>" % escape(GetLicenseMsg())
